package models;

import java.util.LinkedHashMap;
import java.util.List;
import java.util.Map;
import javax.persistence.CascadeType;
import javax.persistence.Entity;
import javax.persistence.Id;
import javax.persistence.OneToMany;
import com.avaje.ebean.Ebean;
import com.avaje.ebean.Page;
import play.data.validation.Constraints;
import play.db.ebean.Model;

/**
 * Model de la Classe Theme.
 * 
 * @author ProjetSI-QCM
 */
@SuppressWarnings("serial")
@Entity
public class Theme extends Model {

    /**
     * Identifiant du Theme.
     */
    @Id
    private Long idTheme;
    /**
     * Liste des Matières d'un Thème.
     */
    private List<Matiere> sesMatieres;
    /**
     * Libelle du Theme.
     */
    @Constraints.Required
    private String libelleT;

    /**
     * Finder de la classe Theme.
     */
    private static Finder<Long, Theme> find = new Finder<Long, Theme>(
            Long.class, Theme.class);

    /**
     * Retourne tous les Themes enregistres.
     * 
     * @return List<Theme> Tous les themes.
     */
    public static List<Theme> findAll() {
        return find.all();
    }

    /**
     * Recherche un Theme grâce à un id.
     * 
     * @param id
     *            L'identifiant du theme
     * @return Theme L'objet recherché
     */
    public static Theme findById(final Long id) {
        return Ebean.find(Theme.class, id);
    }

    /**
     * Permet de sauvegarder un Theme en Base de Données.
     * 
     * @param theme
     *            L'objet à sauvegarder.
     */
    public static void create(final Theme theme) {
        theme.save();
    }

    /**
     * ¨Permet de modifier un Theme en Base de Données.
     * 
     * @param theme
     *            L'objet à modifier.
     */
    public static void update(final Theme theme) {
        theme.update();
    }

    /**
     * Permet de Supprimer un Theme de la base de données.
     * 
     * @param id
     *            L'identifiant du Theme a supprimer.
     */
	public static void delete(final Long id) {
		Theme theme = Theme.findById(id);
		for (Matiere matiere : theme.getSesMatieres()) {
			Matiere.delete(matiere.getIdMatiere());
		}
		find.ref(id).delete();
	}
    
    /**
     * Liste des options pour les listes déroulantes.
     * 
     * @return Map<String,String>
     */
    public static Map<String, String> options() {
        final LinkedHashMap<String, String> options = 
                new LinkedHashMap<String, String>();
        for (Theme c : Theme.find.orderBy("libelleT").findList()) {
            options.put(c.getIdTheme().toString(), c.getLibelleT());
        }
        return options;
    }

    /**
     * Retourne une Page de Theme.
     * 
     * @param page
     *            Page à afficher
     * @param pageSize
     *            Nombre d'objets par page
     * @param sortBy
     *            Propriété utilisée pour le tri
     * @param order
     *            Sens du tri (asc ou desc)
     * @param filter
     *            Filtre appliqué sur le nom de la colonne
     * @return Page<Theme> la page
     */
    public static Page<Theme> page(final int page, final int pageSize,
            final String sortBy, final String order, final String filter) {
        return find.where().ilike("idTheme", "%" + filter + "%")
                .orderBy(sortBy + " " + order).findPagingList(pageSize)
                .setFetchAhead(false).getPage(page);
    }

	/**
	 * @return the idTheme
	 */
	public final Long getIdTheme() {
		return idTheme;
	}

	/**
	 * @param id the idTheme to set
	 */
	public final void setIdTheme(final Long id) {
		this.idTheme = id;
	}

	/**
	 * @return the sesMatieres
	 */
	@OneToMany(mappedBy = "theme", cascade = CascadeType.ALL)
	public final List<Matiere> getSesMatieres() {
		return sesMatieres;
	}

	/**
	 * @param l the sesMatieres to set
	 */
	public final void setSesMatieres(final List<Matiere> l) {
		this.sesMatieres = l;
	}

	/**
	 * @return the libelleT
	 */
	public final String getLibelleT() {
		return libelleT;
	}

	/**
	 * @param l the libelleT to set
	 */
	public final void setLibelleT(final String l) {
		this.libelleT = l;
	}

    
    
}
